﻿using System;
using System.Web;
using System.Xml;

namespace Agile.Crm4.Plugins.FilteredLookup
{
    /// <summary>
    /// You can find a filterxml example in the attached 'filterxml.samples.txt' document.
    /// The logic behind the extraction of the fetchxml filter:
    /// 1.  If the current page (pageUrl) is lookupsingle.aspx, it means the Grid just loaded, 
    ///     then we need to examine the QueryString to find filterxml key.
    /// 2.  If the currnet page (pageUrl) is AppGridWebService.asmx, it means the Grid called 'Refresh' 
    ///     (or searched, which causes the same event).
    ///     In that case, we need to examine the QueryString of the [Http_Referer] page.
    /// </summary>
    public class AdditionalFilterAdapter
    {
        private string key;
        private string pageUrl;
        private string pageReferer;
        private string entityName;
        public AdditionalFilterAdapter(string key, string entityName, string pageUrl, string pageReferer)
        {
            this.key = key;
            this.pageUrl = pageUrl;
            this.pageReferer = pageReferer;
            this.entityName = entityName;
        }

        /// <summary>
        /// 
        /// </summary>
        /// <returns></returns>
        public string GetAdditionalFilter()
        {
            var isInGridWebservice = new Uri(pageUrl, UriKind.Absolute).LocalPath.ToLower().EndsWith("appgridwebservice.asmx");
            if (isInGridWebservice)
                return GetConditionFromUrl(this.pageReferer);
            else
                return GetConditionFromUrl(this.pageUrl);
        }

        private string GetConditionFromUrl(string url)
        {
            var uri = new Uri(url, UriKind.Absolute);
            
            var localPath = uri.LocalPath.ToLower();

            if (localPath.EndsWith("lookupsingle.aspx") == false && localPath.EndsWith("lookupmulti.aspx") == false)
                return null;

            var filters = HttpUtility.ParseQueryString(uri.Query)[key]; 
            if(string.IsNullOrEmpty(filters))
                return null;

            string filter = GetMatchingFilterForEntity(filters, entityName);

            return filter;

        }

        private string GetMatchingFilterForEntity(string element, string entityName)
        {
            try
            {
                if (string.IsNullOrEmpty(element))
                    return null;

                var xmlDoc = new XmlDocument();
                xmlDoc.LoadXml(element);

                var filterNode = xmlDoc.SelectSingleNode(string.Format(@"//filter[@entity='{0}' or not(@entity)]", entityName));
                if (filterNode == null)
                    return null;

                var entityNameNode = filterNode.Attributes["entity"];
                if (entityNameNode != null)
                    entityNameNode.OwnerElement.RemoveAttributeNode(entityNameNode);



                return filterNode.OuterXml;
            }

            catch(XmlException xmlException)
            {
                //TODO: Add log here, if neccassary.
                return null;
            }

        }

        private string GetFilterFromURI(Uri uri)
        {
            var nvc = HttpUtility.ParseQueryString(uri.Query);
            var value = nvc[this.key];
            return value;
        }

        

    }
}
